/**
 * 
 */
package x.java.net;

import java.net.URLStreamHandler;
import java.net.URLStreamHandlerFactory;
import java.util.HashMap;
import java.util.Map;
import java.util.StringTokenizer;

/**
 * @author qiangli
 * 
 */
public class VStreamHandlerFactory implements URLStreamHandlerFactory {
	private Map<String, Class<? extends URLStreamHandler>> handlers = new HashMap<String, Class<? extends URLStreamHandler>>();

	public VStreamHandlerFactory() {
		handlers.put("v", x.java.net.URLStreamHandler.class);
		//handlers.put("http", sun.net.www.protocol.http.Handler.class);
		//handlers.put("https", sun.net.www.protocol.https.Handler.class);
	    //handlers.put("ftp", sun.net.www.protocol.ftp.Handler.class);      
	    //handlers.put("mailto", sun.net.www.protocol.mailto.Handler.class);    
	    //handlers.put("file", sun.net.www.protocol.file.Handler.class);   
	    //handlers.put("jar", sun.net.www.protocol.jar.Handler.class);   
	}

	public void setHandler(String protocol, Class<? extends URLStreamHandler> handler) {
		handlers.put(protocol.toLowerCase(), handler);
	}

	public Class<? extends URLStreamHandler> getHandler(String protocol) {
		return handlers.get(protocol.toLowerCase());
	}

	public URLStreamHandler createURLStreamHandler(String protocol) {
		String pkgs = System.getProperty("java.protocol.handler.pkgs");
		if (pkgs != null) {
			StringTokenizer st = new StringTokenizer(pkgs, "|");
			while (st.hasMoreTokens()) {
				String cn = st.nextToken() + "." + protocol + ".Handler";
				URLStreamHandler h = load(cn);
				if (h != null) {
					return h;
				}
			}
		}
		Class<? extends URLStreamHandler> cl = handlers.get(protocol.toLowerCase());
		if (cl != null) {
			try {
				return cl.newInstance();
			} catch (Exception e) {
			}
		}
		return null;
	}

	private URLStreamHandler load(String className) {
		try {
			Class<?> cl = Class.forName(className);
			Object obj = cl.newInstance();
			if (obj instanceof URLStreamHandler) {
				return (URLStreamHandler) obj;
			}
		} catch (Throwable e) {
		}
		return null;
	}
}
